import React, {RefObject} from 'react';
import {GridContent} from '@ant-design/pro-layout';
import styles from './style.less';
import {Menu, message, Avatar, Tag, Badge} from 'antd';
import Chat from './components/Chat';
import {SelectedItem, selectedType} from './data';
import {connect} from 'dva';
import {User} from '@/models/data';
import {UserModelState} from '@/models/connect';
import SimpleBar from 'simplebar-react';
import 'simplebar/dist/simplebar.min.css';
import {ModelState} from '@/pages/system/notice/model';

import ChatIo from '@/utils/chat';

const MenuItem = Menu.Item;

interface IState {
  selectedItem: SelectedItem;
}

interface IProps {
  user: User;
  chatIM: ModelState;
  dispatch: any;
}

class Index extends React.Component<IProps, IState> {
  state: IState = {
    selectedItem: {type: '', id: 0},
  };

  io: ChatIo | null = null;

  componentDidMount() {
    const {dispatch} = this.props;
    dispatch({
      type: 'chatIM/fetchRecords',
    });

    const token = sessionStorage.getItem('token');
    this.io = new ChatIo(token as string);

    this.io
      .on('online', data => {
        this.online(data);
      })
      .on('offline', data => {
        this.offline(data);
      })
      .on('secretChat', data => {
        this.receiveMessage(data.userId, data.message, {type: 'user', id: data.userId});
      })
      .on('groupChat', data => {
        this.receiveMessage(data.userId, data.message, {type: 'room', id: data.roomId});
      })
      .start()
      .heartbeat(45);
  }

  chatRef: RefObject<any> = React.createRef();

  componentWillUnmount(): void {
    this.io && this.io.close();
  }

  componentDidUpdate() {
    console.log('更新5555');
  }

  // static getDerivedStateFromProps(props: any, state: any) {
  //   console.log('getDerivedStateFromProps');
  //   console.log(props);
  //   console.log(state);
  // }

  online = (data: any) => {
    message.info('已上线');
    const {
      dispatch,
      chatIM: {userList},
    } = this.props;
    userList.map(item => {
      if (item.id == data.user.id) {
        console.log('online');
        item.online_status = 'online';
      }
    });
    dispatch({
      type: 'chatIM/userOnOffLine',
      payload: userList,
    });
  };

  offline = (data: any) => {
    const user = data.user;
    const {
      dispatch,
      chatIM: {userList},
    } = this.props;
    userList.map(item => {
      if (item.id == user.id) {
        item.online_status = 'offline';
      }
    });
    dispatch({
      type: 'chatIM/userOnOffLine',
      payload: userList,
    });
  };

  sendMessage = (message: string, callback: () => void) => {
    const {user, chatIM, dispatch} = this.props;
    const {selectedItem} = this.state;

    const recordsMap = {
      user: {
        recordsType: 'secretRecords',
        badge: 'userBadge',
        saveRecords: 'saveSecretRecords',
        sendData: {
          data: {
            message,
            senderUserId: user.id,
            acceptUserId: selectedItem.id,
          },
          channel: 'secretChat',
        },
      },
      room: {
        recordsType: 'roomRecords',
        badge: 'roomBadge',
        saveRecords: 'saveRoomRecords',
        sendData: {
          data: {
            message,
            roomId: selectedItem.id,
            userId: user.id,
          },
          channel: 'groupChat',
        },
      },
    };
    const records = {...chatIM[recordsMap[selectedItem.type].recordsType]};

    if (!records[selectedItem.id]) {
      records[selectedItem.id] = [];
    }

    records[selectedItem.id].push({userId: user.id, message: message});
    dispatch({
      type: `chatIM/${recordsMap[selectedItem.type].saveRecords}`,
      payload: records,
    }).then(() => {
      callback();
      const data = JSON.stringify(recordsMap[selectedItem.type].sendData);
      console.log(data);
      this.io && this.io.send(data);
    });
  };

  receiveMessage = (userId: number, message: string, receiveItem: SelectedItem) => {
    console.log('receiveMessage');
    console.log(receiveItem);
    const {chatIM, dispatch} = this.props;
    const {selectedItem} = this.state;

    const recordsMap = {
      user: {recordsType: 'secretRecords', badge: 'userBadge', saveRecords: 'saveSecretRecords'},
      room: {recordsType: 'roomRecords', badge: 'roomBadge', saveRecords: 'saveRoomRecords'},
    };

    const records = {...chatIM[recordsMap[receiveItem.type].recordsType]};

    console.log(chatIM);
    console.log(receiveItem.type);
    const receiveId = receiveItem.id.toLocaleString();
    console.log(receiveId);

    if (!records[receiveId]) {
      records[receiveId] = [];
    }

    console.log(records[receiveId]);

    records[receiveId].push({userId, message});

    let badge = null;
    if (selectedItem.id != receiveItem.id) {
      badge = {...chatIM[recordsMap[receiveItem.type].badge]};
      if (!badge[receiveId]) {
        badge[receiveId] = 1;
      } else {
        badge[receiveId]++;
      }
    }

    dispatch({
      type: `chatIM/${recordsMap[receiveItem.type].saveRecords}`,
      payload: records,
      badge,
    }).then(() => {
      if (selectedItem.id == receiveItem.id) {
        this.chatRef.current.scrollToBottom();
      }
    });
  };

  selectedClearBadge = (id: string, type: selectedType) => {
    const badgeMap = {
      user: {stateKey: 'userBadge', reducer: 'saveUserBadge'},
      room: {stateKey: 'roomBadge', reducer: 'saveRoomBadge'},
    };

    const {chatIM, dispatch} = this.props;
    const badge = {...chatIM[badgeMap[type].stateKey]};

    if (badge[id]) {
      badge[id] = 0;
    }
    dispatch({
      type: `chatIM/${badgeMap[type].reducer}`,
      payload: badge,
    });
  };

  render() {
    const {selectedItem} = this.state;
    const {user, chatIM} = this.props;
    return (
      <GridContent>
        <div className={styles.main}>
          <div className={styles.leftMenu}>
            <SimpleBar style={{maxHeight: 600}}>
              <Menu
                mode={'inline'}
                onClick={({key}) => {
                  const keyArr = key.split('_');
                  let selectedItem: SelectedItem;

                  selectedItem = {
                    id: parseInt(keyArr[1]),
                    type: keyArr[0] as selectedType,
                  };
                  //
                  this.selectedClearBadge(keyArr[1], keyArr[0] as selectedType);

                  this.setState(
                    {
                      selectedItem: selectedItem,
                    },
                    () => {
                      this.chatRef.current.scrollToBottom();
                    },
                  );

                  // setTimeout(() => {
                  //   this.chatRef.current.scrollToBottom();
                  // });
                }}
              >
                {chatIM.roomList.map(item => {
                  return (
                    <MenuItem key={'room_' + item.id} style={{height: 46}}>
                      <Badge
                        count={chatIM.roomBadge[item.id] || 0}
                        style={{
                          height: '15px',
                          lineHeight: '15px',
                          minWidth: '15px',
                          position: 'absolute',
                          top: 5,
                          right: 0,
                        }}
                      >
                        <Avatar
                          src={item.avatar_url}
                          size={38}
                          style={{backgroundColor: '#87d068'}}
                        />
                      </Badge>
                      <div style={{display: 'inline-block', marginLeft: 5}}>
                        <Tag color={'#2B2B2B'}>群组</Tag>
                        {item.title}
                      </div>
                    </MenuItem>
                  );
                })}

                <Menu.Divider/>
                {chatIM.userList.map(item => {
                  return (
                    <MenuItem key={'user_' + item.id} style={{height: 46}}>
                      <Badge
                        count={chatIM.userBadge[item.id] || 0}
                        style={{
                          height: '15px',
                          lineHeight: '15px',
                          minWidth: '15px',
                          position: 'absolute',
                          top: 5,
                          right: 0,
                        }}
                      >
                        <Avatar
                          src={item.avatar_url}
                          size={36}
                          style={{backgroundColor: '#87d068'}}
                        />
                      </Badge>

                      <div style={{display: 'inline-block', marginLeft: 5}}>
                        {item.online_status === 'online' ? (
                          <Tag color={'#87d068'}>在线</Tag>
                        ) : (
                          <Tag color={'#ADADAD'}>离线</Tag>
                        )}
                        {item.username}
                      </div>
                    </MenuItem>
                  );
                })}
              </Menu>
            </SimpleBar>
          </div>
          <div className={styles.right}>
            <Chat
              user={user}
              selectedItem={selectedItem}
              sendMessage={this.sendMessage}
              ref={this.chatRef}
              chatIM={chatIM}
              resetSelected={() => {
                this.setState({
                  selectedItem: {type: '', id: 0},
                });
              }}
            />
          </div>
        </div>
      </GridContent>
    );
  }
}

export default connect(({user, chatIM}: { user: UserModelState; chatIM: ModelState }) => ({
  user: user.currentUser,
  chatIM,
}))(Index);
